package com.vhall.component.service.preparation.impl;

import cn.hutool.core.date.DatePattern;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.io.file.FileNameUtil;
import cn.hutool.core.util.IdUtil;
import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.vhall.component.dao.preparation.InviteMapper;
import com.vhall.component.dao.preparation.RoomInvitesMapper;
import com.vhall.component.entity.preparation.InviteCardsEntity;
import com.vhall.component.entity.preparation.RoomInvitesEntity;
import com.vhall.component.entity.preparation.vo.*;
import com.vhall.component.entity.room.dto.RoomJoinsEntityDTO;
import com.vhall.component.entity.room.dto.RoomsEntityDTO;
import com.vhall.component.framework.common.exception.BusinessException;
import com.vhall.component.plugin.common.constant.RedisKey;
import com.vhall.component.plugin.common.constant.RoomConstant;
import com.vhall.component.plugin.common.exception.BizErrorCode;
import com.vhall.component.plugin.core.service.OssService;
import com.vhall.component.service.preparation.InviteCardService;
import com.vhall.component.service.room.RoomInnerService;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import java.text.MessageFormat;
import java.time.LocalDateTime;

/**
 * @author guoxin.wang
 * @date 2021/7/8 15:30
 */
@Slf4j
@Service
public class InviteCardServiceImpl implements InviteCardService {

    @Autowired
    private RedisTemplate redisTemplate;

    @Autowired
    private OssService ossService;

    @Autowired
    private InviteMapper inviteMapper;

    @Autowired
    private RoomInvitesMapper roomInvitesMapper;

    @Autowired
    private RoomInnerService roomInnerFacade;

    /**
     * 获取邀请卡状态
     *
     * @param roomId 房间编号
     * @return 1:存在|0:不存在
     */
    private int getStatus(String roomId) {
        Integer status = (Integer) redisTemplate.opsForHash().get(RedisKey.INTERACT_GLOBAL + roomId, RoomConstant.OPEN_INVITE_CARD);
        if (null != status) {
            return status;
        }
        return 0;
    }

    /**
     * 根据roomId获取邀请卡信息
     *
     * @param roomId 房间编号
     * @return
     */
    private InviteCardsEntity info(String roomId) {
        LambdaQueryWrapper<InviteCardsEntity> wrapper = Wrappers.lambdaQuery();
        wrapper.eq(InviteCardsEntity::getRoomId, roomId)
                .orderByDesc(InviteCardsEntity::getId)
                .last(" limit 1 ");
        return inviteMapper.selectOne(wrapper);
    }

    @Override
    public SetInviteCardRespVO<InviteCardsEntity> setInviteCard(SetInviteCardReqVO reqVO) {
        SetInviteCardRespVO<InviteCardsEntity> result = new SetInviteCardRespVO<>();
        // 1、根据roomid查询。
        InviteCardsEntity inviteCard = info(reqVO.getRoomId());
        // 2、如果为空的话就新建一个。
        if (ObjectUtil.isEmpty(inviteCard)) {
            RoomsEntityDTO roomInfo = roomInnerFacade.getRoomsEntityInfo(reqVO.getRoomId());
            InviteCardsEntity createParam = new InviteCardsEntity();
            createParam.setRoomId(reqVO.getRoomId());
            createParam.setTitle(roomInfo.getSubject());
            createParam.setCompany("");
            createParam.setDate(DateUtil.format(roomInfo.getStartTime(), DatePattern.NORM_DATETIME_PATTERN));
            createParam.setDescription(roomInfo.getSubject());
            createParam.setShowType(1);
            createParam.setImgType(1);
            createParam.setIsShowWatermark(0);
            inviteMapper.insert(createParam);
            inviteCard = createParam;
        }
        RoomJoinsEntityDTO host = roomInnerFacade.getHostUserInfoByRoomId(reqVO.getRoomId());
        String nickName = "";
        if (host != null && StringUtils.isNotEmpty(host.getNickname())) {
            nickName = host.getNickname();
        }
        // 3、构建返回值
        result.setStatus(getStatus(reqVO.getRoomId()));
        result.setInfo(inviteCard);
        result.setNickName(nickName);
        return result;
    }

    @Override
    public Boolean updateInviteCard(UpdateInviteCardReqVO reqVO) {
        InviteCardsEntity param = new InviteCardsEntity();
        LambdaUpdateWrapper<InviteCardsEntity> wrapper = Wrappers.lambdaUpdate();
        wrapper.eq(InviteCardsEntity::getRoomId, reqVO.getRoomId());
        BeanUtils.copyProperties(reqVO, param);
        return inviteMapper.update(param, wrapper) > 0;
    }

    @Override
    public String switchInviteCard(SwitchInviteCardReqVO reqVO) {
        redisTemplate.opsForHash().put(RedisKey.INTERACT_GLOBAL + reqVO.getRoomId(), RoomConstant.OPEN_INVITE_CARD, Integer.valueOf(reqVO.getStatus()));
        return "1";
    }

    @Override
    public UploadInviteCardRespVO upload(UploadInviteCardReqVO reqVo) {
        UploadInviteCardRespVO result = new UploadInviteCardRespVO();
        try {
            String name = IdUtil.fastSimpleUUID();
            String ext = FileNameUtil.extName(reqVo.getFile().getOriginalFilename());
            name = name + "." + ext;
            MultipartFile image = reqVo.getFile();
            String type = image.getContentType();
            String ossResult = ossService.upload(image.getInputStream(), name, type);
            log.info("文件上传结果,{}", ossResult);
            result.setImgUrl(ossResult);
        } catch (Exception ex) {
            log.error("图片上传失败:", ex);
        }
        return result;
    }

    @Override
    public GetInviteCardRespVO getInviteCard(GetInviteCardReqVO reqVO) {
        GetInviteCardRespVO result = new GetInviteCardRespVO();
        int status = getStatus(reqVO.getRoomId());
        if (0 == status) {
            throw new BusinessException(BizErrorCode.COMP_INVITE_CARD_DISABLE);
        }
        InviteCardsEntity inviteCard = info(reqVO.getRoomId());
        RoomJoinsEntityDTO joinUser = roomInnerFacade.getRoomJoinInfo(StringUtils.isEmpty(reqVO.getInviteId()) ? 0 : Integer.parseInt(reqVO.getInviteId()), reqVO.getRoomId());
        String nickName = "主办方";
        if (joinUser != null && StringUtils.isNotEmpty(joinUser.getNickname())) {
            nickName = joinUser.getNickname();
        }
        result.setInfo(inviteCard);
        result.setNickName(nickName);
        return result;
    }

    @Override
    public GetInviteCardRespVO getInviteCardNoException(GetInviteCardReqVO reqVO) {
        GetInviteCardRespVO result = new GetInviteCardRespVO();
        int status = getStatus(reqVO.getRoomId());
        if (0 == status) {
            log.warn(MessageFormat.format("当前房间：【{0}】没有开启邀请卡！", reqVO.getRoomId()));
            return null;
        }
        InviteCardsEntity inviteCard = info(reqVO.getRoomId());
        RoomJoinsEntityDTO joinUser = roomInnerFacade.getRoomJoinInfo(StringUtils.isEmpty(reqVO.getInviteId()) ? 0 : Integer.parseInt(reqVO.getInviteId()), reqVO.getRoomId());
        String nickName = "主办方";
        if (joinUser != null && StringUtils.isNotEmpty(joinUser.getNickname())) {
            nickName = joinUser.getNickname();
        }
        result.setInfo(inviteCard);
        result.setNickName(nickName);
        return result;
    }

    @Override
    public Boolean joinInvite(JoinInviteCardReqVO reqVO) {
        if (StringUtils.isEmpty(reqVO.getRoomId())) {
            reqVO.setRoomId("0");
        }
        if (null == reqVO.getInviteId()) {
            reqVO.setInviteId(0);
        }
        if (null == reqVO.getBeInviteId()) {
            reqVO.setBeInviteId(0);
        }
        RoomInvitesEntity param = new RoomInvitesEntity();
        param.setRoomId(reqVO.getRoomId());
        param.setInviteId(reqVO.getInviteId());
        param.setBeInvitedId(reqVO.getBeInviteId());
        LocalDateTime now = LocalDateTime.now();
        param.setCreatedAt(now);
        param.setUpdatedAt(now);
        return roomInvitesMapper.insert(param) > 0;
    }


}
